package com.eastfair.imaster.controller;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.eastfair.annotation.annotation.base.BaseControllerInfo;
import com.eastfair.annotation.base.SubjectTypeEnum;
import com.eastfair.boot.controller.SuperController;
import com.eastfair.boot.request.PageParams;
import com.eastfair.cache.redis.RedisOps;
import com.eastfair.config.dto.FormFieldDTO;
import com.eastfair.config.vo.ObjectFormFieldEditVO;
import com.eastfair.imaster.dto.ProductPageQuery;
import com.eastfair.imaster.dto.ProductSaveDTO;
import com.eastfair.imaster.dto.ProductUpdateDTO;
import com.eastfair.imaster.entity.Product;
import com.eastfair.imaster.service.ProductService;
import com.eastfair.imaster.vo.ExhibitorVo;
import com.eastfair.imaster.vo.ProductVo;
import com.eastfair.constant.BusinessConstant;
import com.eastfair.core.base.R;
import com.eastfair.core.context.ContextUtil;
import com.eastfair.core.exception.code.ExceptionCode;
import com.eastfair.core.utils.ConvertUtil;
import com.eastfair.echo.core.EchoService;
import com.eastfair.enums.AuditStateEnum;
import com.eastfair.security.formfield.ConvertByFormField;
import com.eastfair.vo.VoProductClass;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;


/**
 * <p>
 * 前端控制器
 * 产品表
 * </p>
 *
 * @author liuxiaobai
 * @date 2021-08-19
 */
@Slf4j
@Validated
@RestController
@RequestMapping("/product")
@Api(value = "Product", tags = "产品表")
public class ProductController extends SuperController<ProductService, Long, Product, ProductPageQuery, ProductSaveDTO, ProductUpdateDTO> {

    @Autowired
    private EchoService echoService;
    @Autowired
    ConvertByFormField convertByFormField;
    @Autowired
    private RedisOps redisOps;

    @Override
    public void handlerResult(IPage<Product> page) {
        // 想让返回值实现自动回显，请将此行代码打开
        echoService.action(page);
    }
    /**
     * Excel导入后的操作
     *
     * @param list
     */
    @Override
    public R<Boolean> handlerImport(List<Map<String, String>> list){
        List<Product> productList = list.stream().map((map) -> {
            Product product = Product.builder().build();
            //TODO 请在这里完成转换
            return product;
        }).collect(Collectors.toList());

        return R.success(baseService.saveBatch(productList));
    }

    /**
     * 分页获取产品
     * @param params 分页参数
     * @return
     */
    @ApiOperation(value = "分页获取产品",notes = "分页获取产品")
    @PostMapping("/queryPage")
    @BaseControllerInfo(voGroup = {VoProductClass.SimpleInfo.class})
    public R<Page<ProductVo>> queryPage(@RequestBody PageParams<ProductPageQuery> params){
        ProductPageQuery query = params.getModel();
        QueryWrapper<Product> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda()
                .like(!StrUtil.isEmpty(query.getName()),Product::getName,query.getName())
                .eq(!StrUtil.isEmpty(query.getVerifyState()),Product::getVerifyState,query.getVerifyState())
                .eq(query.getIsEnable() != null,Product::getIsEnable,query.getIsEnable())
                .eq(Product::getIsDelete, BusinessConstant.DELETE_NO)
                .eq(query.getCompanyId() != null,Product::getCompanyId,query.getCompanyId())
                //产品列表排序：序号正序＞更新时间倒序＞创建时间倒序
                .orderByAsc(Product::getSequence)
                .orderByDesc(Product::getUpdateTime)
                .orderByDesc(Product::getCreateTime);
        Page<Product> page = this.baseService.page(params.buildPage(),queryWrapper);
        return success(ConvertUtil.convertPage(page,ProductVo.class));
    }

    /**
     * 获取产品详情
     * @param query id
     * @return 产品vo
     */
    @ApiOperation(value = "获取产品详情",notes = "获取产品详情")
    @PostMapping("/getDetail")
    public R<ProductVo> getDetail(@RequestBody ProductPageQuery query) {
        if (query.getId() == null) {
            return fail(ExceptionCode.ILLEGAL_ARGUMENT_EX);
        }
        Product product = this.baseService.getById(query.getId());
        ProductVo productVo = new ProductVo();
        //转vo
        BeanUtil.copyProperties(product,productVo);
        //todo 还需拼装问卷

        return success(productVo);
    }

    /**
     * 获取产品详情配置项
     * @param query id
     * @return 产品vo
     */
    @ApiOperation(value = "获取产品详情配置项",notes = "获取产品详情配置项")
    @PostMapping("/getDetailForm")
    public R<List<ObjectFormFieldEditVO>> getDetailForm(@RequestBody ProductPageQuery query) {
        if (query.getId() == null) {
            return fail(ExceptionCode.ILLEGAL_ARGUMENT_EX);
        }
        Product product = this.baseService.getById(query.getId());
        ProductVo productVo = new ProductVo();
        //转vo
        BeanUtil.copyProperties(product,productVo);
        FormFieldDTO formFieldDTO = new FormFieldDTO();
        formFieldDTO.setIsPerfectInfo(BusinessConstant.YES);
        formFieldDTO.setSubjectType(SubjectTypeEnum.PRODUCT.name());
        return convertByFormField.objectConvertFormFieldEditVO(productVo, formFieldDTO);
    }

    /**
     * 保存草稿
     * @param updateDTO
     * @return
     */
    @ApiOperation(value = "保存草稿",notes = "保存草稿")
    @PostMapping("/saveDraft")
    public R<Boolean> saveDraft(@RequestBody ProductUpdateDTO updateDTO){
        R<ProductUpdateDTO> productR = convertByFormField.editFormFieldVOConvertObject(updateDTO.getObjectFormFieldEditVOList(),ProductUpdateDTO.class);
        if (R.SUCCESS_CODE != productR.getCode()) {
            return fail("保存失败");
        }
        updateDTO = productR.getData();
        Product product;
        if (updateDTO.getId() == null) {
            product = new Product();
        } else {
            product = this.baseService.getById(updateDTO.getId());
        }

        if (AuditStateEnum.PENDING.name().equals(product.getVerifyState())){
            return fail(ExceptionCode.PRODUCT_AUDIT_LOCKING);
        }

        BeanUtil.copyProperties(updateDTO,product);
        product.setIsDraft(BusinessConstant.ENABLE_YES);
        if (product.getId() == null) {
            product.setVerifyState(AuditStateEnum.BLANK.name());
            this.baseService.save(product);
        } else {
            this.baseService.updateByIdOfShard(product);
        }
        return success();
    }

    /**
     * 批量编辑产品（仅限可见范围、上架下架）
     * @param query ids、enabled、scope
     * @return
     */
    @ApiOperation(value = "批量编辑产品",notes = "批量编辑产品")
    @PostMapping("/batchUpdate")
    public R<Boolean> batchUpdate(@RequestBody @Validated(ProductPageQuery.BatchValid.class) ProductPageQuery query){
        if (query.getScope() == null && query.getIsEnable() == null) {
            return fail(ExceptionCode.ILLEGAL_ARGUMENT_EX);
        }
        return this.baseService.updateBatch(query);
    }

    /**
     * 批量发布产品
     * @param query ids、scope
     * @return 发布失败的产品名集合
     */
    @ApiOperation(value = "批量发布产品",notes = "批量发布产品")
    @PostMapping("/batchPublish")
    public R<List<String>> batchPublish(@RequestBody @Validated(ProductPageQuery.BatchValid.class) ProductPageQuery query){

        return this.baseService.updateBatchPublish(query.getIds(),ContextUtil.getExhibitionId());
    }

    /**
     * 批量审核产品
     * @param query ids、scope
     * @return 发布失败的产品名集合
     */
    @ApiOperation(value = "批量审核产品",notes = "批量审核产品")
    @PostMapping("/batchAudit")
    public R<Boolean> batchAudit(@RequestBody @Validated(ProductPageQuery.BatchValid.class) ProductPageQuery query){
        AuditStateEnum auditState = AuditStateEnum.get(query.getVerifyState());
        if (auditState == null) {
            return fail(ExceptionCode.ILLEGAL_ARGUMENT_EX);
        }
        //todo 自动审核接入？
        return this.baseService.updateBatchAudit(query.getIds(),auditState,query.getVerifyContent());
    }
}
